数组中&a与&a[0]的区别

数组中&a与&a[0](即a)的区别

​ 在newcoder上写数组相关题目时遇到了这样一个问题:

1
2
3
4
5
//以下 C 语言指令:
int a[5] = {1,3,5,7,9};
int *p = (int *)(&a+1);
printf(“%d,%d”,*(a+1) , *(p-1));
//运行结果是什么?

​ 读者可以先自己思考一下这个问题~ 在这道题中,*(a+1)的输出结果是非常常规容易思考的,而*(int*)(&a+1)的输出结果则需要一定的思考。

​ 下面公布正确答案:3,9。

​ 题目中首先定义了一个可以存在

​ 题目中首先定义了存放5个int类型空间大小的内存,然后初始化5个数。我们知道直接使用数组的名字a表示的是一个指向数组首地址的指针,所以直接a与&a[0]是相同的意思,都表示数组的首地址。所以(a+1)很好理解,假设a地址是0x1000,就是取(0x1000+sizeof(int))地址的数,由于数组的物理地址是连续的,当然就是取2。
  那&a表示什么意思呢,相当于取存放指向数组首地址的指针的存储地址,话有些绕,但是细细品味你就会发现,它就相当于二维指针,假设每个一维指针指向一排数组(当然除了第一个一维数组的指针之外实际都没有申请,但是在访问野指针之前计算机也不知道那块地址是否存在,但的确可以由物理地址连续性来获取这块地址的表示),**所以简言之&a表示第一排数组,&a+1就是表示第二排数组(就是5\
sizeof(int)=54=20空间大小后一段空间的首地址)。**
  有了上面的介绍就好理解了,
(ptr-1)是表示取(0x1000+5sizeof(int)-sizeof(int))地址中的数,算得为5。
  总结:
  *&a[0]表示数组的首地址,与直接a相同意义。而&a表示存储指向数组首地址的指针的地址,可以用二维指针来理解。

*(int*)(&a+1)